package il.ac.bgu.soa2009.hw6.impl;

import il.ac.bgu.soa2009.hw5.ClientPortType;
import il.ac.bgu.soa2009.hw5.RestaurantServiceServiceLocator;
import il.ac.bgu.soa2009.hw5.schema.*;
import org.apache.log4j.Logger;
import org.apache.axis.AxisFault;

import javax.xml.rpc.ServiceException;
import java.rmi.RemoteException;
import java.util.Date;
import java.util.concurrent.Callable;

public class RestaurntReservationTask implements Callable<BooleanResponse> {
    private static Logger logger = Logger.getLogger(RestaurntReservationTask.class);
    private RestaurantServiceServiceLocator[] restaurntLocators;
    private String reservationName;
    private RestaurantType restaurantType;
    private Time time;
    private Date date;
    private RestaurantServiceServiceLocator usedLocator;

    public RestaurntReservationTask(String reservationName,
                                    RestaurantType restaurantType, Time time, Date date,
                                    RestaurantServiceServiceLocator[] restaurntLocators) {
        this.restaurntLocators = restaurntLocators;
        this.reservationName = reservationName;
        this.restaurantType = restaurantType;
        this.time = time;
        this.date = date;
    }

    public BooleanResponse call() throws RemoteException, ServiceException {
        BooleanResponse res = new BooleanResponse();
        usedLocator = getRestaurantLocatorForType(restaurantType.getValue());
        if (usedLocator == null) {
            throw new AxisFault("No such restaurnt type. Please Try another.");
        }//else continue
        ClientPortType clientRestaurantService = usedLocator.getClientRestaurantService();
        TableReservation reservation = new TableReservation();
        reservation.setCostumerName(new ReservationName(reservationName));
        reservation.setDate(date);
        reservation.setTime(time);
        res = clientRestaurantService.reserveTable(reservation);
        res.setValue(true);
        return res;
    }


    private RestaurantServiceServiceLocator getRestaurantLocatorForType(String typeName) {
        for (int i = 0; i < GoOutServiceImpl.getRestaurantCount(); i++) {
            try {
                ClientPortType clientRestaurantService = restaurntLocators[i].getClientRestaurantService();
                RestaurantDetails restaurantDetails = clientRestaurantService.getRestaurantDetails();
                if (typeName != null && typeName.trim().equals(restaurantDetails.getType().getValue().trim())) {
                    return restaurntLocators[i];
                }
            } catch (ServiceException e) {
                logger.error("Could not access restaurant: " + i, e);
            } catch (RemoteException e) {
                logger.error("Error while accessing restaurant: " + i, e);
            }
        }
        return null;
    }

    public RestaurantServiceServiceLocator getUsedLocator() {
        return usedLocator;
    }
}
